﻿using System;
using System.Windows;
using System.Windows.Documents;

namespace CodeCounsel.SharePoint.RibbonDesigner.View.AttachedBehaviors
{
    abstract class DragManager
    {
        DraggedAdorner _draggedAdorner;
        AdornerLayer _adornerLayer;

        public object DraggedData { get; protected set; }
        public FrameworkElement SourceItemContainer { get; protected set; }
        public IDragProcessor DragProcessor { get; private set; }

        protected DataTemplate DragTemplate
        {
            get { return DragDropHelper.GetDragDropTemplate(SourceItemContainer); }
        }

        public bool CanDrag
        {
            get { return DragProcessor.CanDrag(DraggedData); }
        }

        protected DragManager(IDragProcessor dragProcessor)
        {
            if (dragProcessor == null)
            {
                throw new ArgumentNullException("dragProcessor");
            }
            DragProcessor = dragProcessor;
        }
        
        public void EnsureDraggedAdorner(Point location, Point initialMousePosition, Vector initialMouseOffset)
        {
            EnsureDraggedAdorner(
                location.X - initialMousePosition.X + initialMouseOffset.X,
                location.Y - initialMousePosition.Y + initialMouseOffset.Y);
        }

        public int RemoveDraggedItem(object draggedItem)
        {
            return DragProcessor.RemoveItem(draggedItem);
        }
        
        public virtual void EnsureDraggedAdorner(double left, double top)
        {
            if (_draggedAdorner == null)
            {
                _adornerLayer = AdornerLayer.GetAdornerLayer(SourceItemContainer);
                _draggedAdorner = new DraggedAdorner(DraggedData,
                    DragTemplate,
                    SourceItemContainer);
                _adornerLayer.Add(_draggedAdorner);
            }
            _draggedAdorner.SetPosition(left, top);
            _adornerLayer.Update(_draggedAdorner.AdornedElement);
        }

        public virtual void RemoveDraggedAdorner()
        {
            if (_draggedAdorner != null)
            {
                _adornerLayer.Remove(_draggedAdorner);
                _draggedAdorner = null;
                _adornerLayer = null;
            }
        }
    }
}
